﻿using System;
using System.Drawing;
using System.Windows.Forms;
using G.Runtime;
using GameDesigner.Source;
using GameDesigner.Source.Displayers;
using GameDesigner.Source.Elements;
using GameDesigner.Source.Widgets;
using GameLibrary.Model;
using GameLibrary.Model.Core;
using Microsoft.VisualBasic.PowerPacks;
using WeifenLuo.WinFormsUI.Docking;
using System.ComponentModel;

namespace GameDesigner
{
    public partial class GameForm : DockContent, System.IDisposable 
    {
        private readonly ShapeContainer _ShapeContainer = new ShapeContainer();
        private readonly GameDef _GameDef = GameDefFactory.Factory.CreateGame();
        private GameDisplayer _GameDisplayer;
        private GameElementDef _ToDeleteElement;

        public GameForm()
        {
            InitializeComponent();
            Init();
        }

        private void Init()
        {
            this._GameDisplayer = new GameDisplayerDT(_GameDef, _ShapeContainer);
            this._Panel1.Controls.Add(this._ShapeContainer);
            this._ShapeContainer.Dock = DockStyle.Fill;

            this._ShapeContainer.Paint += new GridPainter(50).OnPaint;
            this._ShapeContainer.MouseClick += new MouseEventHandler(this.OnMouseClick);
            this._GameDisplayer.ShapeClickedEvent += this.OnShapeClick;
            this.deleteToolStripMenuItem.Click += new EventHandler(this.deleteToolStripMenuItem_Click);

            _GameDef.GameElementDefs.ElementAddedEvent += GameElementDefs_ElementAddedEvent;
            _GameDef.PropertyChanged += OnPropertyChanged;
            
            base.TabText = _GameDef.Name;
            base.Text = _GameDef.Name;
        }
        
        void OnPropertyChanged(object obj, PropertyChangedEventArgs e)
        {
            base.TabText = _GameDef.Name;
            base.Text = _GameDef.Name;
        }
        
        void OnPropertyChangedEvent(object obj, string name) 
        {
        }

        void GameElementDefs_ElementAddedEvent(GameElementDef subject)
        {
            if (ActiveGame.Game != null)
            {
                GameDef game = ActiveGame.Game;
                foreach (GameElementDef e in game.GameElementDefs)
                {
                    SimpleShape shape = this._GameDisplayer.Shapes[e.Location];
                    GameElementDef element = game.GameElementDefs[e.Location];
                    new ElementDisplayerDT(_GameDisplayer, shape, _ShapeContainer);
                }
            }
        }

        public GameDef GameDef
        {
            get { return _GameDef; }
        }

        protected override void OnActivated(EventArgs e)
        {
            base.OnActivated(e);
            ActiveGame.Game = _GameDef;
        }
        
        protected override void Dispose(bool disposing)
        {
            if (disposing && (components != null))
            {
                components.Dispose();
            }
            base.Dispose(disposing);
            
            if (ActiveGame.Game == this._GameDef) 
            {
                ActiveGame.Game = null;
            }
        }

        protected override void OnDeactivate(EventArgs e) 
        {
            base.OnDeactivate(e);
            ActiveGame.Game = null;
        }

        private void OnShapeClick(SimpleShape shape)
        {
            Point point = shape.Location;
            if (!_GameDisplayer.GameDef.GameElementDefs.Contains(new GameLocation(point)))
            {
                GameElementDef element = GameDefFactory.Factory.CreateElement(
                    _GameDisplayer.GameDef, new GameLocation(point));
                _GameDisplayer.GameDef.GameElementDefs.Add(element);
                //element.GameScriptDef.GenerateScript();
            }
        }

        private void OnMouseClick(object sender, MouseEventArgs e)
        {
            GameLocation loc = new GameLocation(e.Location);
            if (_GameDisplayer.GameDef.GameElementDefs.Contains(loc)) {
                _ToDeleteElement = _GameDisplayer.GameDef.GameElementDefs[loc];
                if (e.Button == System.Windows.Forms.MouseButtons.Right)
                {
                    Point p = new Point(e.Location.X, e.Location.Y);
                    _PopupMenu.Show(this._ShapeContainer, p);
                }
            }
        }

        private void deleteToolStripMenuItem_Click(object sender, EventArgs e)
        {
            if (_ToDeleteElement != null)
            {
                _GameDisplayer.GameDef.GameElementDefs.Remove(_ToDeleteElement);
                _ToDeleteElement = null;
            }
        }

    }
}
